package controller

import (
	"net/http"
	"strconv"

	"go-frame/src/server-main/models"
	"go-frame/src/server-main/service"

	common "go-frame/src/server-common"

	"github.com/gin-gonic/gin"
)

type ProductController struct {
	ProductService *service.ProductService
}

func NewProductController(productService *service.ProductService) *ProductController {
	return &ProductController{ProductService: productService}
}

// @Summary Get all products
// @Description Get a list of all products
// @Tags products
// @Accept json
// @Produce json
// @Success 200 {array} models.Product
// @Security ApiKeyAuth
// @Router /products [get]
func (ctrl *ProductController) GetAllProducts(c *gin.Context) {
	products, err := ctrl.ProductService.GetAllProducts()
	if err != nil {
		common.Error(http.StatusInternalServerError, err.Error()).Send(c)
		return
	}
	common.Success(products, "获取所有产品成功").Send(c)
}

// @Summary Create a new product
// @Description Create a new product with the input payload
// @Tags products
// @Accept json
// @Produce json
// @Param product body models.Product true "Product object to be created"
// @Success 200 {object} models.Product
// @Security ApiKeyAuth
// @Router /products [post]
func (ctrl *ProductController) CreateProduct(c *gin.Context) {
	var product models.Product
	if err := c.ShouldBindJSON(&product); err != nil {
		common.Error(http.StatusBadRequest, err.Error()).Send(c)
		return
	}

	if err := ctrl.ProductService.CreateProduct(&product); err != nil {
		common.Error(http.StatusInternalServerError, err.Error()).Send(c)
		return
	}
	common.Success(product, "创建产品成功").Send(c)
}

// @Summary Get product by ID
// @Description Get a single product by its ID
// @Tags products
// @Accept json
// @Produce json
// @Param id path int true "Product ID"
// @Success 200 {object} models.Product
// @Failure 404 {object} object
// @Security ApiKeyAuth
// @Router /products/{id} [get]
func (ctrl *ProductController) GetProductByID(c *gin.Context) {
	id, err := strconv.ParseUint(c.Param("id"), 10, 64)
	if err != nil {
		common.Error(http.StatusBadRequest, "无效的产品ID").Send(c)
		return
	}

	product, err := ctrl.ProductService.GetProductByID(uint(id))
	if err != nil {
		common.Error(http.StatusNotFound, "产品未找到").Send(c)
		return
	}
	common.Success(product, "获取产品成功").Send(c)
}

// @Summary Update product by ID
// @Description Update an existing product by its ID with the input payload
// @Tags products
// @Accept json
// @Produce json
// @Param id path int true "Product ID"
// @Param product body models.Product true "Product object to be updated"
// @Success 200 {object} models.Product
// @Failure 404 {object} object
// @Security ApiKeyAuth
// @Router /products/{id} [put]
func (ctrl *ProductController) UpdateProduct(c *gin.Context) {
	id, err := strconv.ParseUint(c.Param("id"), 10, 64)
	if err != nil {
		common.Error(http.StatusBadRequest, "无效的产品ID").Send(c)
		return
	}

	var product models.Product
	if err := c.ShouldBindJSON(&product); err != nil {
		common.Error(http.StatusBadRequest, err.Error()).Send(c)
		return
	}
	product.ID = uint(id) // Ensure the ID from the path is used

	if err := ctrl.ProductService.UpdateProduct(&product); err != nil {
		common.Error(http.StatusInternalServerError, err.Error()).Send(c)
		return
	}
	common.Success(product, "更新产品成功").Send(c)
}

// @Summary Delete product by ID
// @Description Delete a product by its ID
// @Tags products
// @Accept json
// @Produce json
// @Param id path int true "Product ID"
// @Success 200 {object} object
// @Failure 404 {object} object
// @Security ApiKeyAuth
// @Router /products/{id} [delete]
func (ctrl *ProductController) DeleteProduct(c *gin.Context) {
	id, err := strconv.ParseUint(c.Param("id"), 10, 64)
	if err != nil {
		common.Error(http.StatusBadRequest, "无效的产品ID").Send(c)
		return
	}

	if err := ctrl.ProductService.DeleteProduct(uint(id)); err != nil {
		common.Error(http.StatusNotFound, "产品未找到").Send(c)
		return
	}
	common.Success(nil, "产品删除成功").Send(c)
}
